package com.demo.goodsinfo;

import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.apache.log4j.Logger;
import org.apache.lucene.analysis.Analyzer;
import org.apache.lucene.document.Document;
import org.apache.lucene.document.DoubleField;
import org.apache.lucene.document.Field;
import org.apache.lucene.document.StringField;
import org.apache.lucene.document.TextField;
import org.apache.lucene.index.IndexWriter;
import org.apache.lucene.index.IndexWriterConfig;
import org.apache.lucene.index.TrackingIndexWriter;
import org.apache.lucene.queryparser.classic.QueryParser;
import org.apache.lucene.search.IndexSearcher;
import org.apache.lucene.search.Query;
import org.apache.lucene.search.ScoreDoc;
import org.apache.lucene.search.SearcherFactory;
import org.apache.lucene.search.SearcherManager;
import org.apache.lucene.search.Sort;
import org.apache.lucene.search.SortField;
import org.apache.lucene.search.TopFieldCollector;
import org.apache.lucene.store.RAMDirectory;
import org.apache.lucene.util.Version;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.stereotype.Service;
import org.wltea.analyzer.lucene.IKAnalyzer;

import com.demo.utils.StringUtils;

@Service
public class GoodsInfoServiceImpl implements GoodsInfoService {
	
	Logger logger = Logger.getLogger(GoodsInfoServiceImpl.class);

	@Autowired
	JdbcTemplate mysqlJdbcTemplate;

	@Override
	public List<Map<String, Object>> getAllDatas() {
		String sql = "select id, skuno, title, price, detailhref from goods_info order by setdate desc";
		return mysqlJdbcTemplate.queryForList(sql);
	}

	private IndexWriter indexWriter = null;

	private TrackingIndexWriter trackingIndexWriter = null;

	private SearcherManager searcherManager = null;

	private Analyzer getAnalyzer() {

		return new IKAnalyzer(true);
	}
	
	private boolean indexIsLoaded = false;

	private void initLuceneIndex() throws IOException {

		indexWriter = new IndexWriter(new RAMDirectory(),
				new IndexWriterConfig(Version.LATEST, getAnalyzer()));

		trackingIndexWriter = new TrackingIndexWriter(indexWriter);

		searcherManager = new SearcherManager(indexWriter, true,
				new SearcherFactory());

		List<Map<String, Object>> datas = getAllDatas();
		if (datas != null) {
			for (Map<String, Object> data : datas) {
				if (data == null || data.isEmpty() || data.size() < 1)
					continue;

				Document doc = new Document();
				for (Map.Entry<String, Object> entry : data.entrySet()) {
					String key = entry.getKey();
					String value = "" + entry.getValue();
					if (StringUtils.isNotNullOrEmpty(key)
							&& StringUtils.isNotNullOrEmpty(value)) {
						if ("price".equals(key)) {
							double priceval = 0;
							try {
								priceval = Double.parseDouble(value);
							} catch (NumberFormatException e) {
							}
							doc.add(new DoubleField(key, priceval,
									Field.Store.YES));
						} else if ("title".equals(key)) {
							doc.add(new TextField(key, value, Field.Store.YES));
						} else {
							doc.add(new StringField(key, value, Field.Store.YES));
						}
					}
				}

				trackingIndexWriter.addDocument(doc);
			}
			indexWriter.commit();
			indexIsLoaded = true;
			logger.info("goodsinfo lucene index load success");
		}
	}

	@Override
	public Map<String, Object> search(String searchText, int start,
			int limit) {
		List<Map<String, String>> datas = new ArrayList<>();
		int total = 0;
		try {
			if(!indexIsLoaded){
				initLuceneIndex();
			}
			
			// 刷新searcherManager,获取最新的IndexSearcher
			searcherManager.maybeRefresh();
			IndexSearcher indexSearcher = searcherManager.acquire();

			//分词
			QueryParser parser = new QueryParser("title", getAnalyzer());
			Query query = parser.parse(searchText);

			// 排序
			Sort sort = new Sort();
			SortField sortField = new SortField("price", SortField.Type.DOUBLE);
			sort.setSort(sortField);
			
			//分页
			TopFieldCollector results = TopFieldCollector.create(sort, start+limit, false, false, false, false);
			indexSearcher.search(query, results);
			total = results.getTotalHits();
			ScoreDoc[] hits = results.topDocs(start, limit).scoreDocs;
			
			if (hits != null && hits.length > 0) {
				for (int i = 0; i < hits.length; i++) {
					Document document = indexSearcher.doc(hits[i].doc);
					Map<String, String> row = new HashMap<String, String>();
					row.put("skuno", document.get("skuno"));
					row.put("title", document.get("title"));
					row.put("price", document.get("price"));
					row.put("detailhref", document.get("detailhref"));
					datas.add(row);
				}
			}
		} catch (Exception e) {
			e.printStackTrace();
		}
		
		Map<String, Object> map = new HashMap<String, Object>();
		map.put("datas", datas);
		map.put("total", total);
		return map;
	}

}
